Cancellable Function
Submission https://leetcode.com/problems/design-cancellable-function/submissions/1479735064/
/**
* @param {Generator} generator
* @return {[Function, Promise]}
*/
//IMPORTANT DETAIL: This is SYNC generator. And not ASYNC.
var cancellable = function(generator) {
let canceled = false;
const cancel = () => {
canceled = true;
}
const promise = new Promise((resolve, reject) => {
const next = async (err, pastValue) => {
const handleIfDone = async (done, value) => {
if(done){
try {
const resolvedValue = await value;
return resolve(resolvedValue);
} catch(err){
return reject(err);
}
}
Promise.resolve(value)
.then((resolvedValue) => setImmediate(next.bind(this, canceled ? 'Cancelled' : null, resolvedValue)))
.catch((err) => setImmediate(next.bind(this, canceled ? 'Cancelled' : err)));
}
try {
const { done, value } = (err || canceled) ? generator.throw(err || 'Cancelled') : generator.next(pastValue);
await handleIfDone(done, value);
} catch(err){
return reject(err);
}
}
setImmediate(next);
})
return [cancel, promise];
}
module.exports.cancellable = cancellable;